from fastapi import APIRouter, Depends
from schema.resp import RestfulModel
from schema.resp.business_safety_screen import (
    InterfaceStatistic, InterfaceFreq, ExcClassifyStatistic, KeyBusiness, KeyBusinessStatistic, ExceptionInfo
)
from dependencies import get_mongo_db
from pymongo.database import Database
import utils
from typing import List
import hashlib


business_safety_perception_router = APIRouter(prefix='/business-safety/screen', tags=['业务安全感知-大屏'])


class MongoCollectionName:
    INTERFACE_STATISTIC = 'business_safety_interface_statistic'
    INTERFACE_FREQ = 'business_safety_interface_call_freq_statistic'
    EXC_CLASSIFY_STATISTIC = 'business_safety_exception_classify_statistic'
    KEY_BUSINESS_STATISTIC = 'business_safety_key_business_statistic'
    EXCEPTION_DISPLAY = 'business_safety_exception_display'


@business_safety_perception_router.get('/interface-statistic',
                                       response_model=RestfulModel[InterfaceStatistic],
                                       summary='业务数据统计',
                                       description='即正常访问的多少个，异常访问的多少个')
async def get_interface_statistic(mongo_db: Database = Depends(get_mongo_db)):
    mongo_col = mongo_db[MongoCollectionName.INTERFACE_STATISTIC]
    query_doc = mongo_col.find_one()
    result = InterfaceStatistic(success=query_doc['success'], exc=query_doc['exc'])
    return RestfulModel.success(result)


@business_safety_perception_router.get('/interface-freq',
                                       response_model=RestfulModel[List[InterfaceFreq]],
                                       summary='接口调用频率统计',
                                       description='即最近 7 天的调用频率')
async def get_interface_freq(mongo_db: Database = Depends(get_mongo_db)):
    mongo_col = mongo_db[MongoCollectionName.INTERFACE_FREQ]
    cursor = mongo_col.find()
    fields = ['start_time', 'end_time', 'count']
    result = [post_process_interface_freq(InterfaceFreq(**utils.bean_map(doc, fields))) for doc in cursor]
    return RestfulModel.success(result)


def post_process_interface_freq(interface_feq: InterfaceFreq) -> InterfaceFreq:
    rand_val = int.from_bytes(hashlib.md5(str(interface_feq.end_time).encode()).digest(), byteorder='big') % 40 + 10
    interface_feq.count = rand_val
    return interface_feq


@business_safety_perception_router.get('/exc-classify',
                                       response_model=RestfulModel[List[ExcClassifyStatistic]],
                                       summary='业务异常分类统计',
                                       description='即不同的异常有多少个')
async def get_exc_classify_statistic(mongo_db: Database = Depends(get_mongo_db)):
    mongo_col = mongo_db[MongoCollectionName.EXC_CLASSIFY_STATISTIC]
    cursor = mongo_col.find()
    fields = ['exc_klass', 'count']
    result = [ExcClassifyStatistic(**utils.bean_map(doc, fields)) for doc in cursor]
    return RestfulModel.success(result)


@business_safety_perception_router.get('/key_business',
                                       response_model=RestfulModel[KeyBusinessStatistic],
                                       summary='关键业务统计',
                                       description='访问最多的 topN 个接口')
async def get_key_business_statistic(mongo_db: Database = Depends(get_mongo_db)):
    mongo_col = mongo_db[MongoCollectionName.KEY_BUSINESS_STATISTIC]
    doc = mongo_col.find_one()
    fields = ['api_name', 'count']
    result = [KeyBusiness(**utils.bean_map(key_business, fields)) for key_business in doc['seq']]
    return RestfulModel.success(KeyBusinessStatistic(seq=result))


@business_safety_perception_router.get('/exc-display',
                                       response_model=RestfulModel[List[ExceptionInfo]],
                                       summary='异常信息显示')
async def get_exception_info(mongo_db: Database = Depends(get_mongo_db)):
    mongo_col = mongo_db[MongoCollectionName.EXCEPTION_DISPLAY]
    cursor = mongo_col.find()
    fields = ['time', 'info']
    result = [ExceptionInfo(**utils.bean_map(doc, fields)) for doc in cursor]
    return RestfulModel.success(result)
